package repository

import (
	"context"
	"strconv"

	"gitee.com/thewalkers/refactoring-code/model"
	"gitee.com/thewalkers/refactoring-code/model/apperrors"
	"github.com/jmoiron/sqlx"
	"go.uber.org/zap"
)

// MysqlEmployeeRepository is data/repository implementation
// of service layer EmployeeRepository
type MysqlPayCheckRepository struct {
	DB *sqlx.DB
}

// NewEmployeeRepository is a factory for initializing Employee Repository
func NewPayCheckRepository(db *sqlx.DB) model.PaycheckRepository {
	return &MysqlPayCheckRepository{
		DB: db,
	}
}

// Create reaches out to database SQLX api
func (m *MysqlPayCheckRepository) Create(ctx context.Context, p *model.Paycheck) error {
	query := `INSERT INTO paychecks (employee_id, gross_pay, net_pay, deduction) VALUES(?, ?, ?, ?)`

	if _, err := m.DB.Exec(query, p.EmployeeID, p.GrossPay, p.NetPay, p.Deduction); err != nil {
		zap.L().Error("repository could not create a paycheck with err: ", zap.Error(err))
		return apperrors.NewInternal()
	}

	return nil
}

// FindByID -> give the id of Paychecks, and return Payments
func (m *MysqlPayCheckRepository) FindByID(ctx context.Context, id int64) (*model.Paycheck, error) {
	payment := &model.Paycheck{}

	query := `SELECT * FROM paychecks where id = ?`

	if err := m.DB.Get(payment, query, id); err != nil {
		zap.L().Error("repository cound not get a paychecks with err: ", zap.Error(err))
		return nil, apperrors.NewNotFound("id", strconv.Itoa(int(id)))
	}

	return payment, nil
}

// Update update Paychecks
func (m *MysqlPayCheckRepository) Update(ctx context.Context, p *model.Paycheck) error {
	query := `UPDATE paychecks SET employee_id = ?, gross_pay = ?, net_pay = ?, deduction = ? WHERE id = ?`

	if _, err := m.DB.Exec(query, p.EmployeeID, p.GrossPay, p.NetPay, p.Deduction, p.ID); err != nil {
		zap.L().Error("repository could not update a paycheck with err: ", zap.Error(err))
		return apperrors.NewInternal()
	}

	return nil
}
